package com.example.sample.activity;

import android.content.pm.PackageInfo;
import android.os.Bundle;
import android.text.Editable;
import android.text.InputFilter;
import android.text.Spanned;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

import com.example.app.BaseActivity;
import com.example.sample.R;

import net.liteheaven.xblib.common.rom.ApkUtil;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class ApkInfoActivity extends BaseActivity {

    private TextView mTvOutput;
    private EditText mEtInput;    
    private Button mBtnOk;
    private EditText mEtTextChecker;
    private Button mEtTextCheckerOk;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_apk_info);
        mTvOutput = (TextView)findViewById(R.id.tvOutput);
        String content = "";        
        mTvOutput.setText(content);
        mEtInput = (EditText)findViewById(R.id.etInput);
        mBtnOk = (Button)findViewById(R.id.btnOk);
        mBtnOk.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                onClickOk();
            }
        });
        mEtTextChecker = (EditText)findViewById(R.id.etTextChecker);
        mEtTextCheckerOk = (Button)findViewById(R.id.btnTextCheckerOk);
        mEtTextCheckerOk.setOnClickListener(new View.OnClickListener() {
			
			@Override
			public void onClick(View v) {
				String str = mEtTextChecker.getText().toString();
				
				String output = "";
				
				output += ">>>>>>>>>>\n";
				byte bytes [] = str.getBytes();
				for (int i = 0; i < bytes.length; i++) {
					int val = bytes[i];
					val = val & 0xff;
					output += ""+i+"> " + val+"\n";
				}
				output += "<<<<<<<<<<\n";

                output += ">>>>>>>>>>\n";
                char[] ca = str.toCharArray();
                for (int i = 0; i < ca.length; i++) {
                    char c = ca[i];
                    long vv = Long.valueOf(c);
                    output += ""+i+"> " + vv +"\n";
                }
                output += "<<<<<<<<<<\n";
                output += "len = " + bytes.length;

                output += str;
				showText(output);
			}
		});
        
        findViewById(R.id.btnTextCheckerAdd).setOnClickListener(new View.OnClickListener() {
			
			@Override
			public void onClick(View v) {

                String str = mEtTextChecker.getText().toString();
                int val = 0;
                try{
                    val = Integer.valueOf(str, 16);
                }catch (Exception e){
                    //
                }

                char cl, ch;
                int low, high;

                if (val < 0xffff){
                    low = val;
                    high = 0;
                    cl = (char)val;
                    ch = 0;
                }else{
                    int left = val - 0x10000;

                    // 取低位
                    low = 0xdc00 + (left & 0x3ff);

                    // 高位
                    high = 0xd800 + (left >> 10 & 0x3ff);

                    cl = (char)low;
                    ch = (char)high;
                }

                String constructed = new String(new char[] {ch, cl});
                //String constructed = new String(new int[] {val}, 0, 1);

                String print = String.format("%s h = 0x%X(%d)   l = 0x%X(%d)", constructed, high, high, low, low);

                showText(print);

				/*View decorView = ApkInfoActivity.this.getWindow().getDecorView();
				View focusView = decorView.findFocus();
				if (focusView instanceof EditText){
					EditText et = (EditText)focusView;
					String output = "当前焦点为:\n" + et.toString();
					output += "\n" + transformed;
					showText(output);
				}*/
			}
		});

        EditText et = findViewById(R.id.noEmojiEditText);
        et.setFilters(new InputFilter[]{new LengthAndEmoijFilter(10)});

        boolean s = Character.isHighSurrogate("握草".charAt(1));
        int a = 0;
    }

    private void onClickOk(){
        Editable e = mEtInput.getText();
        String input = "";
        if (e!=null){
            input = e.toString();
        }
        PackageInfo pi = ApkUtil.getPackageInfo(this, input);
        StringBuffer sb = new StringBuffer("暂无信息");
        if (pi!=null){
            sb = ApkUtil.getPackageInfoReport(pi);
        }
        mTvOutput.setText(sb);
    }
    
    private void showText(String str){
    	mTvOutput.setText(str);
    }

    /**
     * Java String用的编码方式是UTF-16，UTF-16取值范围为U+0~U+10FFFF。
     * charAt方法获取的值对应这个16位数的值。
     * 16位中D800~DFFF为保留位。
     * 当16位不够用时，就用32位。
     * 怎么判断16位是一个字符还是一个32位字符的高位或低位呢？
     * 一个16位完整字符，不会取D800~DFFF范围内的值
     * 当一个16位的值为D800~DBFF说明它是一个32位字符的高位，在DC00~DFFF说明它是低位。
     *
     * U+1ffff怎么拆分成两个16byte呢？
     * 因为低位范围为DC00~DFFF，C转换为2进制为1100，这个00加上低位的一个字节总共10byte可供支配。
     * 高位为D800~DBFF，同理一样有10byte可供支配。
     * 所以算法出来了，把1ffff这20byte，高10byte加上0xD800得到高位，低10byte加上0xDC00得到低位
     *
     * String转换为BYTE数组之后，编码方式改为UTF-8。
     * UTF-8编码比较有意思，判断一个byte是多字节看最高位是不是1，如果是11代表接下来一个byte和本byte构成一个字符
     * 类似如果是111代表接下来2个byte和本byte构成一个字符。
     */
    public static class LengthAndEmoijFilter implements InputFilter {

        private int mMax;

        public LengthAndEmoijFilter(int max) {
            mMax = max;
        }
        public CharSequence filter(CharSequence source, int start, int end,
                                   Spanned dest, int dstart, int dend) {
            //判断是否含有emoji表情
            if (isHasEmoji(source)) {
                return "";
            }

            /**
             * 下面这段拷贝自LengthFilter
             */
            int keep = mMax - (dest.length() - (dend - dstart));
            if (keep <= 0) {
                return "";
            } else if (keep >= end - start) {
                return null; // keep original
            } else {
                keep += start;
                if (Character.isHighSurrogate(source.charAt(keep - 1))) {
                    --keep;
                    if (keep == start) {
                        return "";
                    }
                }
                return source.subSequence(start, keep);
            }
        }

        public static boolean isHasEmoji(CharSequence source) {
            Pattern emoji = Pattern.compile("[\u00a1-\u00af]|[\u203c-\u3299]|[\ud83c\udc00-\ud83c\udfff]|[\ud83d\udc00-\ud83d\udfff]|[\ud83e\udc00-\ud83e\udfff]", Pattern.UNICODE_CASE | Pattern.CASE_INSENSITIVE);
            Matcher emojiMatcher = emoji.matcher(source);
            if (emojiMatcher.find()) {
                return true;
            }
            return false;
        }
    }
}
